注意:所有文章除特别说明外,转载请注明出处.
[TOC]
第一章 并发编程的挑战
1.1 上下文切换
时间片:CPU通过每个线程分配CPU时间片来实现单核处理器多线程执行代码。时间片是分配给每一个线程的时间,因为很短,通常是几十毫秒。所以会有多个线程同时执行的错觉。
注意:当并发执行累加操作不超过百万次时,速度会比串行执行累加操作慢。这是因为线程有创建和上下文切换的开销。
提示:减少上下文切换的方法有无锁并发编程、CAS算法、使用最少线程和使用协程。
1.无锁并发编程:多线程竞争锁时会引起上下文切换,所以多线程开发时尽量避免使用锁。如:将数据的ID按照Hash算法取模分段,不同的线程处理不同段的数据。
2.CAS:Java的Atomic包使用CAS算法来更新数据,不需要加锁。
3.使用尽量少的线程:避免创建不需要的线程。如:任务少,而创建大量的线程。
4.协程:在单线程里实现多任务的调度,并在单线程里维持多个任务间的切换。
1.1.4 减少上下文切换实战
1.2 死锁
提示:一旦出现死锁,业务是可感知的,因为不能继续提供服务了,那么只能通过dump线程查看到底哪个线程出现问题。
1.2.1 避免死锁的常用方法
1.避免一个线程同时获取多个锁。
2.避免一个线程在锁内同时占用多个资源,尽量保证每个锁只占用一个资源。
3.尝试使用定时锁,使用 `lock.tryLock(timeout)` 来替代使用内部锁机制。
4.对于数据库锁,加锁和解锁必须在一个数据库连接里面,否则会出现解锁失败情况。
1.3 资源限制挑战
资源限制表示在并发编程时,程序的执行速度受限于计算机硬件资源或软件资源。硬件资源限制有:带宽的上传/下载速度、硬盘读写速度和CPU的处理速度。软件资源有:数据库的连接数和socket连接数等。
因为资源限制的问题,在并发程序执行的过程中,程序执行不仅不会变快,还可能会更慢,因为增加了上下文的切换和资源调度的时间。
对于硬件资源限制解决方法:集群并行执行程序。
对于软件资源限制解决方法:资源池复用。
1.4 同步
“同步”这个术语包括:关键字synchronized,volatile类型的变量,显式锁(Explicit Lock)以及原子变量。